﻿using System;
using System.Web.Mvc;
using System.Web.Security;
using System.Linq;
using System.Collections.Generic;
using System.Reflection;
using System.ComponentModel.DataAnnotations;
using System.Web;
using MasterSheetManager.Models;

[AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, AllowMultiple = false, Inherited = true)]
public sealed class AllowAnonymousAttribute : Attribute { }


public class LogonRequired : AuthorizeAttribute
{
    public override void OnAuthorization(AuthorizationContext filterContext)
    {

        bool skipAuthorization = filterContext.ActionDescriptor.IsDefined(typeof(AllowAnonymousAttribute), true)
            || filterContext.ActionDescriptor.ControllerDescriptor.IsDefined(typeof(AllowAnonymousAttribute), true);

        var name = HttpContext.Current.User.Identity.Name;
        if (!string.IsNullOrEmpty(name) || skipAuthorization == true)
        {
            FormsAuthentication.SetAuthCookie(name, true);
        }
        else
        {
            filterContext.Result = new HttpUnauthorizedResult();
        }

        base.OnAuthorization(filterContext);
    }


    protected override bool AuthorizeCore(HttpContextBase httpContext)
    {
        if (HttpContext.Current.User != null)
        {
            return true;
        }
        return false;
    }

    public class RoleRequired : AuthorizeAttribute
    {


        public RoleRequired()
        {

        }



        public virtual int? MinLevel { get; set; }
        public virtual int? MaxLevel { get; set; }

        public virtual int Level { get; set; }
        public override void OnAuthorization(AuthorizationContext filterContext)
        {
            bool skipAuthorization = filterContext.ActionDescriptor.IsDefined(typeof(AllowAnonymousAttribute), true)
            || filterContext.ActionDescriptor.ControllerDescriptor.IsDefined(typeof(AllowAnonymousAttribute), true);
            var level = Employee.CurrentRoleLVL;

            if (MinLevel != null && MaxLevel != null)
            {
                if (level >= MinLevel && level <= MaxLevel)
                {
                    skipAuthorization = true;
                }
                else if (MinLevel == null && level <= MaxLevel)
                {
                    skipAuthorization = true;
                }

            }
            else if (level >= Level)
            {
                skipAuthorization = true;
            }


            if (!skipAuthorization)
            {
                filterContext.Result = new HttpUnauthorizedResult();

                base.OnAuthorization(filterContext);
            }
        }
    }

    public sealed class DirectorRequired : RoleRequired
    {
        public const int LVL = RoleLevel.Director;
        public override int Level
        {
            get { return LVL; }
        }
    }

    public sealed class ResouceManagerRequired : RoleRequired
    {
        public const int LVL = RoleLevel.ResourceManager;
        public override int Level
        {
            get { return LVL; }
        }
    }


    public sealed class ManagerRequired : RoleRequired
    {
        public const int LVL = RoleLevel.Manager;
        public override int Level
        {
            get { return LVL; }
        }
    }

    /// <summary>
    /// 100
    /// </summary>
    /// 
    public sealed class ExcutionRequired : RoleRequired
    {
        public const int LVL = RoleLevel.Excution_Others;
        public override int? MinLevel
        {
            get
            {
                return RoleLevel.Excution_Others;
            }

        }

        public override int? MaxLevel
        {
            get
            {
                return RoleLevel.Excution_Sales;
            }
        }

    }
    public sealed class ExcutionSalesRequired : RoleRequired
    {
        public const int LVL = RoleLevel.Excution_Sales;
        public override int Level
        {
            get { return LVL; }
        }
    }

    public sealed class ExcutionConferenceRequired : RoleRequired
    {
        public const int LVL = RoleLevel.Excution_Conference;
        public override int Level
        {
            get { return LVL; }
        }
    }

    public sealed class ExcutionCPRequired : RoleRequired
    {
        public const int LVL = RoleLevel.Excution_CP;
        public override int Level
        {
            get { return LVL; }
        }
    }

    public sealed class ExcutionDesignerRequired : RoleRequired
    {
        public const int LVL = RoleLevel.Excution_Designer;
        public override int Level
        {
            get { return LVL; }
        }
    }

    public sealed class ExcutionOthersRequired : RoleRequired
    {
        public const int LVL = RoleLevel.Excution_Others;
        public override int Level
        {
            get { return LVL; }
        }
    }

    public sealed class ExcutionMarketRequired : RoleRequired
    {
        public const int LVL = RoleLevel.Excution_Market;
        public override int Level
        {
            get { return LVL; }
        }
    }


    public sealed class AdministratorRequired : RoleRequired
    {
        public const int LVL = RoleLevel.Administrator;
        public override int Level
        {
            get { return LVL; }
        }

        /// <summary>
        /// Override authriztion method for admin.
        /// </summary>
        /// <param name="filterContext">Default para.</param>
        public override void OnAuthorization(AuthorizationContext filterContext)
        {
            //Judging against login user rather than current user.
            bool loginUserIsAdmin = Employee.LoginUserIsAdmin();
            if (!loginUserIsAdmin)
            {
                filterContext.Result = new HttpUnauthorizedResult();
                base.OnAuthorization(filterContext);
            }
        }

    }

    public class RoleLevel
    {
        public const int Administrator = 99999;
        public const int Director = 1000;
        public const int ResourceManager = 500;
        public const int Manager = 100;
        public const int Excution_Sales = 10;
        public const int Excution_CP = 9;
        public const int Excution_Market = 8;
        public const int Excution_Conference = 7;
        public const int Excution_Designer = 6;
        public const int Excution_Others = 1;
    }
}



